package com.github.xzb617.adm.controller;

import com.github.xzb617.adm.service.RegCenterConfigService;
import com.github.xzb617.domain.common.AjaxResponse;
import com.github.xzb617.domain.common.TextCondition;
import com.github.xzb617.domain.condition.RegCenterInstanceCondition;
import com.github.xzb617.domain.dto.InstanceStatusDTO;
import com.github.xzb617.domain.dto.MetadataDTO;
import com.github.xzb617.domain.entity.RegCenterConfig;
import com.github.xzb617.regcenter.RegCenterService;
import com.github.xzb617.regcenter.common.Application;
import com.github.xzb617.regcenter.common.Instance;
import com.github.xzb617.regcenter.common.enums.ServerStatus;
import org.springframework.web.bind.annotation.*;

import javax.validation.ValidationException;
import java.util.List;
import java.util.stream.Collectors;
import java.util.stream.Stream;

@RestController
@RequestMapping("/regcenter")
public class RegCenterController {

    private final RegCenterService regCenterService;
    private final RegCenterConfigService regCenterConfigService;

    public RegCenterController(RegCenterService regCenterService, RegCenterConfigService regCenterConfigService) {
        this.regCenterService = regCenterService;
        this.regCenterConfigService = regCenterConfigService;
    }

    @GetMapping("/apps")
    public AjaxResponse getApplications(TextCondition condition) {
        RegCenterConfig current = this.regCenterConfigService.getCurrent();
        if (current == null) {
            return AjaxResponse.failure("尚未设置默认的注册中心配置");
        }
        List<Application> apps = this.regCenterService.getApps(current.getRegCenterAddr());
        if (!condition.isEmpty()) {
            apps = apps.stream().filter(app -> app.getId().contains(condition.getSearchText()))
                    .collect(Collectors.toList());
        }
        return AjaxResponse.success().message("查询成功").data(apps);
    }

    @GetMapping("/instances")
    public AjaxResponse getInstances(RegCenterInstanceCondition condition) {
        RegCenterConfig current = this.regCenterConfigService.getCurrent();
        if (current == null) {
            return AjaxResponse.failure("尚未设置默认的注册中心配置");
        }
        if (condition.getAppId() == null) {
            throw new ValidationException("缺少应用ID");
        }
        List<Instance> instances = this.regCenterService.getInstances(current.getRegCenterAddr(), condition.getAppId());
        // 过滤查询条件(有条件的时候才需要过滤)
        if (!condition.isEmpty() || condition.getStatus()!=null) {
            Stream<Instance> stream = instances.stream();
            if (!condition.isEmpty()) {
                stream = stream.filter(instance -> {
                    return instance.getInstanceId().contains(condition.getSearchText()) || instance.getIpAddr().contains(condition.getSearchText());
                });
            }
            if (condition.getStatus()!=null) {
                stream = stream.filter(instance -> instance.getStatus().equals(condition.getStatus()));
            }
            instances = stream.collect(Collectors.toList());
        }
        return AjaxResponse.success().message("查询成功").data(instances);
    }

    @PutMapping("/metadata")
    public AjaxResponse modifyMetadata(@RequestBody MetadataDTO metadataDTO) {
        RegCenterConfig current = this.regCenterConfigService.getCurrent();
        if (current == null) {
            return AjaxResponse.failure("尚未设置默认的注册中心配置");
        }
        boolean result = this.regCenterService.modifyMetadata(current.getRegCenterAddr(), metadataDTO.getAppId(), metadataDTO.getInstanceId(), metadataDTO.getMetadata());
        return result?AjaxResponse.success().message("变更成功"):AjaxResponse.failure("变更失败");
    }

    @PutMapping("/status")
    public AjaxResponse modifyStatus(@RequestBody InstanceStatusDTO dto) {
        RegCenterConfig current = this.regCenterConfigService.getCurrent();
        if (current == null) {
            return AjaxResponse.failure("尚未设置默认的注册中心配置");
        }
        ServerStatus status = Boolean.TRUE.equals(dto.getStatus())? ServerStatus.UP: ServerStatus.DOWN;
        boolean result = this.regCenterService.modifyStatus(current.getRegCenterAddr(), dto.getAppId(), dto.getInstanceId(), status);
        return result?AjaxResponse.success().message("操作成功"):AjaxResponse.failure("操作失败");
    }
}
